package cn.icare.cms.impl;

import cn.icare.cms.*;
import cn.icare.cms.dao.mapper.UserMapper;
import cn.icare.cms.dao.po.User;
import cn.icare.cms.model.ro.EditUserRO;
import cn.icare.cms.model.vo.rest.MsgDatasVO;
import cn.icare.cms.model.vo.rest.UserLoginRespVO;
import cn.icare.cms.model.vo.rest.UserVO;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import tk.mybatis.mapper.entity.Example;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Base64;
import java.util.Date;
import java.util.List;

@Service
public class UserServiceImpl implements UserService {
    @Resource
    private UserMapper userMapper;
    private final Logger logger = LoggerFactory.getLogger(UserServiceImpl.class);
    private final String DECODE_CHARSET = "UTF-8";
    private  final long tokenTime=24*60 * 60 * 1000; //token保持时间24小时

    private  final long refreshTokenTime=7*24*60 * 60 * 1000; //刷新token保持时间7天
    @Override
    public UserLoginRespVO login(String name, String password) {
        UserLoginRespVO result = null;
        try {
            List<User> userDBList = this.getDBList(name);
            if (ListUtil.isNotEmpty(userDBList)) {
                User userDB = userDBList.get(0);
                UserVO userVO = this.toVO(userDB);
                String tempPassword = new String(Base64.getDecoder().decode(password), this.DECODE_CHARSET);
                //对密码进行自定义加密，然后与数据库中加密的密码进行比较
                tempPassword= new PWDUtil().encryptPassword(tempPassword);
                if (userDB.getPassword().equalsIgnoreCase(tempPassword)) {
                   JwtUtil jwtUtil = new JwtUtil();
                   //创建token
                    String token = jwtUtil.createJWT(userDB.getId(), tokenTime);
                    //创建refreshToken
                    String refreshToken= jwtUtil.createJWT(userDB.getId(),refreshTokenTime);
                   // userVO.setPassword(password);
                    result = new UserLoginRespVO();
                    result.setUser(userVO);
                    result.setToken(token);
                    result.setRefreshToken(refreshToken);
                    userDB.setLastlogintime(new Date());
                    this.userMapper.updateByPrimaryKeySelective(userDB);
                }
            }
        } catch (Exception e) {
            this.logger.error("login 异常", e);
        }
        return result;
    }

    @Override
    public void logout(String name, String password) {
        try {
            //addCode 为后续业务做预留
        } catch (Exception e) {
            this.logger.error("logout 异常", e);
        }
    }

    @Override
    public boolean updatePassword(Integer id, String oldPassword, String newPassword) {
        boolean result = false;
        try {
            if (id == null || StringUtil.isEmpty(oldPassword) || StringUtil.isEmpty(newPassword)) {
                this.logger.warn("updatePassword 缺少参数");
                return result;
            }

            User userDB = this.userMapper.selectByPrimaryKey(id);
            String tempPassword = new String(Base64.getDecoder().decode(oldPassword), this.DECODE_CHARSET);
            //对密码进行自定义加密，然后与数据库中加密的密码进行比较
            tempPassword= new PWDUtil().encryptPassword(tempPassword);
            if (userDB == null || !userDB.getPassword().equals(tempPassword)) {
                this.logger.warn("updatePassword 参数错误");
                return result;
            }

            userDB.setPassword(new PWDUtil().encryptPassword(new String(Base64.getDecoder().decode(newPassword), this.DECODE_CHARSET)));
            userDB.setUpdatetime(new Date());
            result = this.userMapper.updateByPrimaryKey(userDB) > 0;
        } catch (Exception e) {
            this.logger.error("updatePassword 异常", e);
        }
        return result;
    }

    @Override
    public Long createOne(UserVO userVO) {
        Long result = -1L;
        try {
            User userDB = this.toDB(userVO);
            Date now = new Date();
            userDB.setCreatetime(now);
            userDB.setUpdatetime(now);
            String tempPassword = new String(Base64.getDecoder().decode(userDB.getPassword()), this.DECODE_CHARSET);
            //对密码进行自定义加密，然后与数据库中加密的密码进行比较
            tempPassword= new PWDUtil().encryptPassword(tempPassword);
            userDB.setPassword(tempPassword);
            if (this.userMapper.insert(userDB) > 0) {
                result = userDB.getId();
            }
        } catch (Exception e) {
            this.logger.error("createOne 异常", e);
        }
        return result;
    }

    @Override
    public boolean deleteOne(Integer id) {
        boolean result = false;
        try {
            result = this.userMapper.deleteByPrimaryKey(id) > 0;
        } catch (Exception e) {
            this.logger.error("deleteOne 异常", e);
        }
        return result;
    }

    @Override
    public boolean deleteBatch(List<Integer> ids) {
        boolean result = false;
        try {
            if (ListUtil.isNotEmpty(ids)) {
                Example example = new Example(User.class);
                Example.Criteria criteria = example.createCriteria();
                criteria.andIn("id", ids);
                result = this.userMapper.deleteByExample(example) > 0;
            }
        } catch (Exception e) {
            this.logger.error("deleteBatch 异常", e);
        }
        return result;
    }

    @Override
    public UserVO getOne(Integer id) {
        UserVO result = null;
        try {
            User userDB = this.userMapper.selectByPrimaryKey(id);
            result = this.toVO(userDB);
        } catch (Exception e) {
            this.logger.error("getOne 异常", e);
        }
        return result;
    }

    @Override
    public MsgDatasVO getList(String name, Integer pageNum, Integer pageSize) {
        PageHelper.startPage(pageNum, pageSize);
        MsgDatasVO result = new MsgDatasVO();
        try {
            Example example = new Example(User.class);
            Example.Criteria criteria = example.createCriteria();
            if (StringUtil.isNotEmpty(name)) {
                criteria.andLike("realname", "%" + name + "%");
            }
            List<User> userDBList = this.userMapper.selectByExample(example);
            PageInfo pageInfo = new PageInfo(userDBList);
            result.setTotal(pageInfo.getTotal());
            List<UserVO> userVOList = new ArrayList<UserVO>();
            if (ListUtil.isNotEmpty(userDBList)) {
                for (User userDB : userDBList) {
                    UserVO userVO = this.toVO(userDB);
                    if (userVO != null) {
                        userVOList.add(userVO);
                    }
                }
            }
            result.setDatas(userVOList);
        } catch (Exception e) {
            this.logger.error("getList 异常", e);
        }
        return result;
    }

    @Override
    public List<User> getDBList(String name) {
        List<User> result = null;
        try {
            Example example = new Example(User.class);
            Example.Criteria criteria = example.createCriteria();
            if (StringUtil.isNotEmpty(name)) {
                criteria.andEqualTo("username", name);
            }
            result = this.userMapper.selectByExample(example);
        } catch (Exception e) {
            this.logger.error("getDBList 异常", e);
        }
        return result;
    }

    @Override
    public boolean isExists(String username) {
        Example example = new Example(User.class);
        Example.Criteria criteria = example.createCriteria();
        if (StringUtil.isNotEmpty(username)) {
            criteria.andEqualTo("username", username);
        }
      List<User> users=  this.userMapper.selectByExample(example);
        if(users!=null && users.size()>0)
        {
            return true;
        }
        return false;
    }

    @Override
    public boolean updateOne(EditUserRO userVO) {
        try {
            User user = new User();
            user.setId(userVO.getId());
            user.setPhone(userVO.getPhone());
            user.setPositionid(userVO.getPositionId());
            if (StringUtil.isNotEmpty(userVO.getPassword())) {
                String tempPassword = new String(Base64.getDecoder().decode(userVO.getPassword()), this.DECODE_CHARSET);
                //对密码进行自定义加密，然后与数据库中加密的密码进行比较
                tempPassword = new PWDUtil().encryptPassword(tempPassword);
                user.setPassword(tempPassword);
            }
           Integer result= this.userMapper.updateByPrimaryKeySelective(user);
            return  result>0;
        }catch (Exception ex)
        {
            this.logger.error("updateOne 异常",ex);
        }
        return  true;
    }

    @Override
    public UserLoginRespVO refreshToken(String token) {

        UserLoginRespVO result = null;
        JwtUtil jwtUtil = new JwtUtil();
        Integer userId =  jwtUtil.parseJWT(token);
        if(userId!=null && userId>0)
        {
            result=new UserLoginRespVO();
            //重新创建 token和refreshToken
            String newToken = jwtUtil.createJWT(userId.longValue(), tokenTime);
            String refreshToken = jwtUtil.createJWT(userId.longValue(), refreshTokenTime);
            result.setToken(newToken);
            result.setRefreshToken(refreshToken);
            return result;
        }
        return null;
    }

    private UserVO toVO(User user) {
        UserVO result = null;
        try {
            if (user != null) {
                result = new UserVO();
                result.setCreateTime(user.getCreatetime());
                result.setId(user.getId());
                result.setPositionId(user.getPositionid());
                result.setUsername(user.getUsername());
                result.setRealname(user.getRealname());
                result.setPassword(user.getPassword());
                result.setPhone(user.getPhone());
                result.setStatus(user.getStatus());
                result.setUpdateTime(user.getUpdatetime());
                result.setLastlogintime(user.getLastlogintime());
            }
        } catch (Exception e) {
            this.logger.error("toVO 异常", e);
        }
        return result;
    }

    private User toDB(UserVO userVO) {
        User result = null;
        try {
            if (userVO != null) {
                result = new User();
                result.setCreatetime(userVO.getCreateTime());
                result.setId(userVO.getId());
                result.setPositionid(userVO.getPositionId());
                result.setUsername(userVO.getUsername());
                result.setRealname(userVO.getRealname());
                result.setPassword(userVO.getPassword());
                result.setUpdatetime(userVO.getUpdateTime());
                result.setStatus(userVO.getStatus());
                result.setPhone(userVO.getPhone());
            }
        } catch (Exception e) {
            this.logger.error("toDB 异常", e);
        }
        return result;
    }
}
